<template>
  <el-form ref="spuForm" :model="spuInfo" :rules="rules" label-width="80px">
    <el-form-item label="SPU名称" prop="spuName">
      <el-input v-model="spuInfo.spuName" placeholder="请输入SPU名称" />
    </el-form-item>
    <el-form-item label="SPU品牌" prop="tmId">
      <el-select v-model="spuInfo.tmId" placeholder="请选择品牌">
        <el-option v-for="trademark in trademarkList" :key="trademark.id" :label="trademark.tmName" :value="trademark.id" />
      </el-select>
    </el-form-item>
    <el-form-item label="SPU描述" prop="description">
      <el-input v-model="spuInfo.description" type="textarea" placeholder="请输入SPU描述" />
    </el-form-item>
    <el-form-item label="SPU图片" prop="spuImageList">
      <el-upload action="/dev-api/admin/product/fileUpload" :class="{ 'spu-image-upload': spuImageList.length >= 3 }" list-type="picture-card" :on-preview="handlePictureCardPreview" :on-remove="handleRemove" :on-success="handleAvatarSuccess" :before-upload="beforeAvatarUpload" accept=".jpg,.png,.jpeg" :limit="3" :file-list="spuImageList">
        <i class="el-icon-plus" />
        <div slot="tip" class="el-upload__tip">只能上传JPG、PNG、JPEG 格式图片，且不超过3M</div>
      </el-upload>
      <el-dialog :visible.sync="dialogVisible">
        <img width="30%" :src="dialogImageUrl" alt="">
      </el-dialog>
    </el-form-item>
    <el-form-item label="销售属性" prop="spuSaleAttrList">
      <el-select v-model="spuInfo.spuSaleAttr" :placeholder="`还剩下${formatBaseSaleAttrList.length}个销售属性`">
        <el-option v-for="baseSaleAttr in formatBaseSaleAttrList" :key="baseSaleAttr.id" :label="baseSaleAttr.name" :value="baseSaleAttr.name" />
      </el-select>
      <el-button type="primary" icon="el-icon-plus" style="margin-left:10px" :disabled="!spuInfo.spuSaleAttr" @click="addSpuSaleAttr">添加销售属性值</el-button>
      <el-table :data="spuInfo.spuSaleAttrList" border style="margin-top:10px">
        <el-table-column type="index" label="序号" align="center" width="80" />
        <el-table-column label="属性名" prop="saleAttrName" width="130" />
        <el-table-column label="属性值列表">
          <template v-slot="{row}">
            <el-tag v-for="tag in row.spuSaleAttrValueList" :key="tag.saleAttrValueName" closable :disable-transitions="false" @close="handleClose(row,tag)">
              {{ tag.saleAttrValueName }}
            </el-tag>
            <el-input v-if="row.inputVisible" ref="saveTagInput" v-model.trim="inputValue" class="input-new-tag" size="small" @keyup.enter.native="handleInputConfirm(row)" @blur="handleInputConfirm(row)" />
            <el-button v-else class="button-new-tag" size="small" @click="showInput(row)">+ 添加属性值</el-button>
          </template>
        </el-table-column>
        <el-table-column label="操作">
          <template v-slot="{$index}">
            <el-tooltip content="删除属性" placement="top">
              <el-button type="danger" icon="el-icon-delete" size="small" @click="deleteSpuSaleAttr($index)" />
            </el-tooltip>
          </template>
        </el-table-column>
      </el-table>
    </el-form-item>
    <el-form-item>
      <el-button type="primary" @click="submitSpuForm">确定</el-button>
      <el-button @click="$emit('update:visible',1)">取消</el-button>
    </el-form-item>
  </el-form>
</template>

<script>
import { reqGetAllTrademarkList, reqGetBaseSaleAttrList, reqSaveSpuInfo, reqGetSpuImageList, reqGetSpuSaleAttrList } from '@/api/product/spu'
import { mapState } from 'vuex'
export default {
  name: 'SaveSpu',
  props: {
    currentSpuInfo: {
      type: Object,
      default: () => {}
    }
  },
  data() {
    const spuImageListValidator = (rule, value, callback) => {
      // 1. 图片列表不能为空
      // if (!value.length) {
      //   // callback(new Error('请至少上传一张图片'))
      //   // return
      //   return callback(new Error('请至少上传一张图片'))
      // }

      // if (!value.length) return callback(new Error('请至少上传一张图片'))

      callback() // 最后一定要调用一次没有参数的callback才表示验证通过
    }
    const spuSaleAttrListValidator = (rule, value, callback) => {
      // 1. 先判断是否选择了某个销售属性
      if (!value.length) {
        callback(new Error('请至少选择一个销售属性'))
        return
      }
      // 2.判断是否添加了具体的销售属性值
      if (!value.every((item) => item.spuSaleAttrValueList.length !== 0)) {
        callback(new Error('请至少添加一个对应的销售属性值'))
        return
      }
      callback()
    }
    return {
      // dynamicTags: ['标签一', '标签二', '标签三'],
      // inputVisible: false,
      inputValue: '',
      dialogImageUrl: '',
      dialogVisible: false,
      trademarkList: [],
      baseSaleAttrList: [],
      spuImageList: [], // 用来存储图片的数组
      spuInfo: {
        // 最终添加SPU时需要收集到的属性有如下：
        spuName: '', // spu名称
        tmId: '', // spu所属品牌
        description: '', // spu的描述
        spuImageList: [], // 照片墙
        // spuSaleAttrList:[
        //   {saleAttrName:'',saleAttrValueList:[]}
        // ], // 销售属性及对应的值
        spuSaleAttr: '', // 选中的销售属性名称 此值不需要发送给服务器 即使发了也没关系
        spuSaleAttrList: [], // 销售属性及对应的值
        // category3Id: ''
        ...this.currentSpuInfo
      },
      rules: {
        spuName: [{ required: true, message: '请输入Spu名称', trigger: 'blur' }],
        tmId: [{ required: true, message: '请选择品牌', trigger: 'change' }],
        description: [{ required: true, message: '请输入SPU描述', trigger: 'blur' }],
        spuImageList: [{ required: true, validator: spuImageListValidator, trigger: 'change' }],
        spuSaleAttrList: [{ required: true, validator: spuSaleAttrListValidator, trigger: 'blur' }]
      }
    }
  },
  computed: {
    formatBaseSaleAttrList() {
      return this.baseSaleAttrList.filter((baseSaleAttr) => {
        return !this.spuInfo.spuSaleAttrList.find((item) => baseSaleAttr.name === item.saleAttrName)
      })
    },
    ...mapState('category', ['category3Id']),
    formatSpuImageList() {
      // return this.spuInfo.spuImageList.map(item => {
      return this.spuImageList.map((item) => {
        return {
          name: item.imgName,
          url: item.imgUrl
        }
      })
    }
  },
  async mounted() {
    // const result1 = await reqGetAllTrademarkList()
    // const result2 = await reqGetBaseSaleAttrList()
    // Promise.all 可以一次性调用多个接口函数,如果成功都成功，有一个失败则全失败 如果成功的话，响应回来的数据是按书写的顺序
    // prmise.race 也可以一次性发送多个请求,抢先机制，谁先回来不一定
    try {
      let promises = [reqGetAllTrademarkList(), reqGetBaseSaleAttrList()]
      const { id } = this.spuInfo
      // 如果id有值的话，说明此是更新操作，需要发送4次请求
      if (id) {
        promises = promises.concat([reqGetSpuImageList(id), reqGetSpuSaleAttrList(id)])
      }
      const [responseTrademarkList, responseBaseSaleAttrList, responseSpuImageList, responseSpuSaleAttrList] = await Promise.all(promises)

      this.trademarkList = responseTrademarkList.data
      this.baseSaleAttrList = responseBaseSaleAttrList.data

      // console.log('abaaa', responseSpuImageList)
      if (responseSpuImageList && responseSpuImageList.code === 200) {
        // this.spuInfo.spuImageList = responseSpuImageList.data
        this.spuImageList = responseSpuImageList.data.map((item) => {
          return {
            name: item.imgName,
            url: item.imgUrl
          }
        })
        this.spuInfo.spuSaleAttrList = responseSpuSaleAttrList.data
      }
    } catch (e) {
      this.$message({
        type: 'error',
        message: '获取数据失败...'
      })
    }
  },
  methods: {
    // 删除图片时调用的函数
    handleRemove(file, fileList) {
      // file是当前被删除了的图片资料
      // fileList是剩余的图片资料
      // console.log(file, fileList)
      // this.spuInfo.spuImageList = fileList
      this.spuImageList = fileList
    },
    // 预览图片时调用的函数
    handlePictureCardPreview(file) {
      console.log(file)
      this.dialogImageUrl = file.url
      this.dialogVisible = true
    },
    // 上传成功后，会调用此方法
    handleAvatarSuccess(res, file, fileList) {
      console.log('success', res, file)
      // 收集上传的图片
      // this.spuInfo.spuImageList = fileList
      this.spuImageList = fileList
      // this.spuInfo.spuImageList = fileList.map(item => {
      //   return {
      //     imgName: item.name,
      //     imgUrl: item.response.data
      //   }
      // })
      // // 上传图片成功之后，移除校验提示
      this.$refs.spuForm.clearValidate(['spuImageList'])
    },
    // 上传之前会调用 此方法
    beforeAvatarUpload(file) {
      // const isJPG = file.type === 'image/jpeg'
      const imgArr = ['image/jpeg', 'image/jpg', 'image/png']
      const isJPG = imgArr.includes(file.type)
      // 1M=1024k  1K=1024byte
      const isLt3M = file.size / 1024 / 1024 < 3

      if (!isJPG) {
        this.$message.error('上传头像图片只能是 JPG、PNG、JPEG 格式!')
      }
      if (!isLt3M) {
        this.$message.error('上传头像图片大小不能超过 3MB!')
      }
      return isJPG && isLt3M
    },
    // 动态编辑标签相关
    handleClose(row, tag) {
      // this.dynamicTags.splice(this.dynamicTags.indexOf(tag), 1)
      // this.spuInfo.spuSaleAttrList.splice(this.spuInfo.spuSaleAttrList.indexOf(tag), 1)
      row.spuSaleAttrValueList.splice(row.spuSaleAttrValueList.indexOf(tag), 1)
    },

    showInput(row) {
      // row.inputVisible = true
      this.$set(row, 'inputVisible', true)
      this.$nextTick((_) => {
        this.$refs.saveTagInput.$refs.input.focus()
      })
    },

    handleInputConfirm(row) {
      const inputValue = this.inputValue

      if (inputValue) {
        if (row.spuSaleAttrValueList.find((item) => item.saleAttrValueName === inputValue)) {
          this.$message.error('属性值不能重复，请重新输入！')
          row.inputVisible = false // 将输入框切换成按钮
          this.inputValue = '' // 清空输入框中的值 以便下一次继续添加
          return
        }

        // 获取属性所对应的id
        const id = this.baseSaleAttrList.find((item) => item.name === row.saleAttrName).id
        row.spuSaleAttrValueList.push({
          baseSaleAttrId: id,
          saleAttrName: row.saleAttrName,
          saleAttrValueName: inputValue
        })
      }
      // this.inputVisible = false
      row.inputVisible = false // 将输入框切换成按钮
      this.inputValue = '' // 清空输入框中的值 以便下一次继续添加
    },
    // 1. 添加销售属性及属性值
    addSpuSaleAttr() {
      const spuSaleAttrList = this.spuInfo.spuSaleAttrList
      // if (spuSaleAttrList.length && spuSaleAttrList[spuSaleAttrList.length - 1].spuSaleAttrValueList.length === 0) {
      //   this.$message.error('请添加具体属性值...')
      //   return
      // }

      if (!spuSaleAttrList.every((item) => item.spuSaleAttrValueList.length !== 0)) {
        this.$message.error('有属性项值为空,请添加完整...')
        return
      }
      const id = this.baseSaleAttrList.find((item) => item.name === this.spuInfo.spuSaleAttr).id
      this.spuInfo.spuSaleAttrList.push({
        baseSaleAttrId: id,
        inputVisible: false,
        saleAttrName: this.spuInfo.spuSaleAttr, // 颜色 尺寸 版本
        spuSaleAttrValueList: []
      })
      // 清空下拉框
      this.spuInfo.spuSaleAttr = ''

      // 清掉校验规则
      this.$refs.spuForm.clearValidate(['spuSaleAttrList'])
    },
    // 2. 删除销售属性及属性值
    deleteSpuSaleAttr(index) {
      this.spuInfo.spuSaleAttrList.splice(index, 1)
    },
    // 3. 添加SPU
    submitSpuForm() {
      this.$refs.spuForm.validate(async (valid) => {
        if (valid) {
          this.spuInfo.category3Id = this.category3Id
          // this.spuInfo.spuImageList = this.spuInfo.spuImageList.map(item => {
          this.spuInfo.spuImageList = this.spuImageList.map((item) => {
            return {
              imgName: item.name,
              imgUrl: item.response ? item.response.data : item.url
            }
          })
          if (!this.spuImageList.length) {
            this.$message.error('请上传至少一张图片')
            return
          }
          const result = await reqSaveSpuInfo(this.spuInfo)
          if (result.code === 200) {
            this.$message.success('添加SPU成功...')
            this.$emit('update:visible', 1)
          } else {
            this.$message.error('添加SPU失败...')
          }
        } else {
          console.log('error submit!!')
          return false
        }
      })
    }
  }
}
</script>

<style>
.el-tag + .el-tag {
  margin-left: 10px;
}
.button-new-tag {
  margin-left: 10px;
  height: 32px;
  line-height: 30px;
  padding-top: 0;
  padding-bottom: 0;
}
.input-new-tag {
  width: 90px;
  margin-left: 10px;
  vertical-align: bottom;
}
</style>
